home *** CD-ROM | disk | FTP | other *** search
- /*
- * A hack to make building other programs easier, by extracting the
- * commands needed to build the file from it's source.
- *
- * build [name NAME] [flags COMMAND=FLAGS ...] [file] FILE [FILE ...]
- *
- * Name defaults to "build". Flags causes the following arguments to be parsed
- * for extra flags to be added to each COMMAND. All input FILEs are scanned
- * for build lines to be issued to the system. If flags is present, file is
- * required.
- *
- * In scanning a file, build ignores all lines until it sees a line containing
- * the string "===NAME", for whatever value name has, defaulting to build. All
- * lines following are then processed until a line containing "===endNAME" is
- * encountered. Delimiter and control are set by parsing the line ===NAME line
- * as '===NAME delimiter DELIMITER control CONTROL'
- *
- * In processing the build lines, two tokens have special significance. They
- * are called delimiter and control, and are normally '%' and ';'. The line is
- * first split on the control character, into the front and back halves. If
- * there is a delimiter in the front half, any text preceding it is discarded.
- * If there is a delimiter in the back half, any text following it is discarded.
- *
- * The front half is treated as a command to be issued to the system. If the
- * first word of the front half is matched by a the command part of a flags
- * argument, then the flags part of that argument is inserted into the command
- * after the first word. I.e. the command issued is "command FLAGS rest of line".
- * The back half of the command is then checked, and the above comamnd is issued
- * if it is called for.
- *
- * The back half is assumed to be of the form 'output= FILE input= FILE ...'.
- * If any of the input files are newer than the output file, then the command
- * in the front half will be executed. If either input or output keywords are
- * missing, the command is always issued.
- *
- * As a convenience, if the back half of a line is empty, then it will be
- * executed if the previous command was executed.
- *
- * Copyright 1991, Mike Meyer
- * All Rights Reserved
- *
- * See the file "Supersaver:Distribution" for information on distribution.
- */
-
- /* Get the support code */
- if ~show('Libraries', 'rexxsupport.library') then do
- if ~addlib('rexxsupport.library', 0, -30) then do
- say "Can't open rexxsupport.library!"
- exit
- end
- end
-
- flags. = ''
- flags = 0
- name = 'build'
- files = ''
-
- /* Parse them arguments */
- args = arg(1)
- do i = 1 to words(args)
- select
- when upper(word(args, i)) = 'NAME' then do
- flags = 0
- i = i + 1
- name = word(args, i)
- end
- when upper(word(args, i)) = 'FILE' then do
- flags = 0
- i = i + 1
- files = word(args, i)
- end
- when upper(word(args, i)) = 'FLAGS' then flags = 1
- when flags then do
- parse value word(args, i) with command '=' flag
- if flag = '' then
- flags.currentcommand = flags.currentcommand word(args, i)
- else do
- currentcommand = command
- flags.command = flag
- end
- end
- otherwise files = files word(args, i)
- end
- end
-
- /*
- * loop over the file names.
- */
- files = expand(files)
- do i = 1 to words(files)
- call buildfile(word(files, i), name)
- end
-
- exit 0
-
- /*
- * Scan a file, looking for the build instructions.
- */
- buildfile: procedure expose flags.
- parse arg file, name
-
- delim = '%'
- control = ';'
-
- if ~open(input, file) then do
- say "Can't open file" file
- return 10
- end
-
- /* Search for the section with command in it */
- search = '==='upper(name)
- do until index(upper(line), search) ~= 0
- if eof(input) then do
- say "No actions found for" name "in file" file
- return 5
- end
- line = readln(input)
- end
-
- /* Check for control/delimter settings */
- parse var line 'control' new .
- if new ~= '' then control = new
- parse var line 'delimiter' new .
- if new ~= '' then delimiter = new
-
- /* Process the command lines */
- search = '===END'upper(name)
- line = readln(input)
- do while index(upper(line), search) = 0
- parse var line command (control) files
-
- /* Check files section */
- parse var files files (delim)
- parse var files "output=" outfile "input=" infiles
- if outfile = "" | infiles = "" then docommand = 1
- else do
- instamp = makestamp(strip(outfile))
- docommand = 0
- do i = 1 to words(infiles)
- if instamp < makestamp(word(infiles, i)) then do
- docommand = 1
- leave
- end
- end
- end
-
- /* Build command to execute */
- parse var command (delim) new flags
- if new ~= "" then command = new
- else parse var command command flags
- if command ~= "" & docommand then do
- say command flags
- address command command flags.command flags
- if rc ~= 0 then exit rc
- end
- line = readln(input)
-
- if eof(input) then do
- say "No end to build section"
- exit 10
- end
- end
-
- call close input
- return 0
-
- /* Get a files creation date as a numeric string */
- makestamp: procedure
- arg filename
-
- parse value statef(filename) with . . . . d m t .
- return right(d, 4, 0) || right(m, 4, 0) || right(t, 4, 0)
-